#ifdef GL_ES
#define LOWP lowp
precision mediump float;
#else
#define LOWP  
#endif

uniform sampler2D u_texture0;

uniform float far; //   1/far
uniform vec4 lightPos;
uniform vec3 lightColor;

varying vec4 v_texCoords;
varying vec3 v_viewRay;


const float shininessFactor = 25.0;

const vec2 bitShifts = vec2(1.0 / 256.0, 1.0);
float unPack(vec2 zz)
{
	zz *= bitShifts;
	return (zz.x + zz.y);
}

void main()
{	
	vec4 texture = texture2DProj(u_texture0,v_texCoords);
	float depth = -unPack(texture.rg);	
		
//	vec2 normal = texture.ba * 2.0 - 1.0;	
//	vec3 surfaceNormal =  vec3(normal, sqrt(1.0 - dot(normal,normal)));
	vec2 fenc = texture.ba * 4.0 - 2.0;
    float f = dot(fenc,fenc);
    vec3 surfaceNormal = (vec3(fenc * sqrt(1.0 - f * 0.25), 1.0 - f * 0.5));
    
		
    
    vec3 viewRay = vec3(v_viewRay.xy * (far / v_viewRay.z), far);
	vec3 vPos = viewRay * depth;
	vec3 fromEye = -normalize(vPos);
	
	vec3 lightDiffer = lightPos.xyz - vPos;
  	float lightDis = length(lightDiffer);
    vec3 lightDir = normalize(lightDiffer);
    
    float diffuse = dot(surfaceNormal, lightDir ); 
		
   //blinn
	vec3 halfAngle = normalize(lightDir + fromEye);
	float specular = pow(clamp(dot(halfAngle, surfaceNormal),0.0,1.0), shininessFactor);
	
	specular = diffuse > 0.0 ? specular : 0.0;	
	
		float intensity = (diffuse + 1.0) *  max(1.0 - lightDis * lightPos.w,0.0);
	
	gl_FragColor = clamp(intensity * vec4(lightColor, specular),0.0,1.0);	
	}